package org.istt.web;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Set;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.istt.domain.Group;
import org.istt.domain.Menu;
import org.istt.domain.User;
import org.istt.service.GroupManager;
import org.istt.service.MenuManager;
import org.istt.service.MenuTreeManager;
import org.istt.service.UserManager;
import org.springframework.beans.factory.annotation.Autowired;

import com.opensymphony.xwork2.ActionContext;

public class GroupAction extends BaseAction<GroupManager, Group, Long> {
    /**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	private final Log log = LogFactory.getLog(GroupAction.class);
	private String cancel;
    private String delete;
    private String search;
    private Group group;

	private List<Menu> lstAllMenu;
	private List<String> lstPermissionMenu;
	private List<Menu> lstSelectedMenu;
	private List<User> users;
	private List<Group> groups;

	private GroupManager mgr;
	private MenuManager menuManager;
	private MenuTreeManager menuTreeManager;
	private UserManager userManager;
    
	public String addUserToGroup(){
    	
    	return SUCCESS;
    }
	public String asign(){
        // check for an add
        if (id != null) {
        	group = mgr.get(getId());
        	users = userManager.getList();
        } else {
        	//TODO nothing
        }        
        
        
        return SUCCESS;
	}
	public String delete() {
        if (log.isDebugEnabled()) {
            log.debug("entering 'delete' method");
        }
        
        if(getId()!=null){
        	Group groupObj = this.mgr.get(getId());
        	List<Object> args = new ArrayList<Object>();
	        args.add(group.getName());
			if(groupObj.getUsers()!=null && groupObj.getUsers().size()!=0){
				log.debug("Not allow delete user");
				ActionContext.getContext().getSession().put("message", getText("group.validation.message.cannotdelete", args));
			}else{
				mgr.remove(group.getId());
		        ActionContext.getContext().getSession().put("message", getText("X\u00F3a th\u00E0nh c\u00F4ng! ", args));
			}
		}
                
        return "delete";
    }
    public String edit() {
        // check for an add
        if (id != null) {
        	group = mgr.get(getId());
        } else {
        	group = new Group();
        }        
        
        this.setLstSelectedMenu(getSelectedMenus());
        this.lstAllMenu = getFullMenus();
        
        return SUCCESS;
    }

    public String execute() {
        if (cancel != null) {
            return "cancel";
        }
        if (delete != null) {
            return delete();
        }
        if (search != null) {
        	return search();
        }
        return SUCCESS;
    }

	public String getCancel() {
		return cancel;
	}
	
    public String getDelete() {
		return delete;
	}	
    
    private List<Menu> getFullMenus(){
		List<Menu> lstResult = new ArrayList<Menu>();
		List<Menu> lstmenu = this.menuManager.getList();
		for (int i = 0; i < lstmenu.size(); i++) {
			Menu mnu = lstmenu.get(i);
			if(mnu.getIsActive()){
				if(mnu.getIsFather()){
					mnu.setName(" + "+mnu.getName());
					lstResult.add(mnu);	
				}else{
					mnu.setName(" --- "+mnu.getName());
					lstResult.add(mnu);
				}
			}
		}
		return lstResult;
	}
    
	public Group getGroup() {
		return group;
	}
	
	public List<Group> getGroups() {
		return groups;
	}
	
	
	public List<?> getLstAllMenu() {
		return lstAllMenu;
	}
	
	public List<String> getLstPermissionMenu() {
		return lstPermissionMenu;
	}
	public List<?> getLstSelectedMenu() {
		return lstSelectedMenu;
	}
	
	public MenuManager getMenuManager() {
		return menuManager;
	}

	public MenuTreeManager getMenuTreeManager() {
		return menuTreeManager;
	}

	public GroupManager getMgr() {
		return mgr;
	}

	public String getSearch() {
		return search;
	}

	private List<Menu> getSelectedMenus(){
		List<Menu> lstResult = new ArrayList<Menu>();
		if(this.group!=null){
			Set<Menu> setMenu = this.group.getMenus();
	    	if(setMenu.size()!=0){
	    		List<Menu> lstmenu = this.menuManager.getList();
	    		for (int i = 0; i < lstmenu.size(); i++) {
					Menu mnu = lstmenu.get(i);
					if(setMenu.contains(mnu) && mnu.getIsActive()){
						if(mnu.getIsFather()){
							lstResult.add(mnu);	
						}else{
							lstResult.add(mnu);
						}
					}
				}
	    	}	
		}
		
		return lstResult;
	}

	public UserManager getUserManager() {
		return userManager;
	}
    public List<User> getUsers() {
		return users;
	}
    public String list() { 
    	List<Group> lstGroups = mgr.getList();
    	groups = new ArrayList<Group>();
    	for (Iterator<Group> iterator = lstGroups.iterator(); iterator.hasNext();) {
			Group grp = (Group) iterator.next();
			if(grp.getRoleSystem()!=null && grp.getRoleSystem() && (grp.getAuthority().equals("ROLE_USER") || grp.getAuthority().equals("ROLE_MODERATOR"))){
			//TODO: do not add to list
			}else{
				this.groups.add(grp);
			}
		}
        return SUCCESS; 
    }
    
    public String loadSearch() {
        if (log.isDebugEnabled()) {
            log.debug("entering 'load search' method");
        }		
		return SUCCESS;
	}

    public String save() {
        if (log.isDebugEnabled()) {
            log.debug("entering 'save' method");
        }
        
        if(this.lstPermissionMenu!=null){
        	log.debug("------------------Total menus: "+ lstPermissionMenu.size());
        	Set<Menu> menus = new HashSet<Menu>();
        	for (int i = 0; i < lstPermissionMenu.size(); i++) {
        		
				Menu mnu = this.menuManager.getMenuById(lstPermissionMenu.get(i));
				if(mnu!=null){
					// ADD Child
					if(!mnu.getIsFather()){
						Menu father = this.menuTreeManager.getFatherMenu(mnu.getId().toString());
						if(father!=null && father.getId() != mnu.getId()){
							if(!lstPermissionMenu.contains(father.getId().toString()) && !menus.contains(father)){
								menus.add(father); 
							}
						}	
					}
					log.debug("------------------Add menu: "+ mnu.getName());
					// Is Father => add
					menus.add(mnu);
				}
			}
        	this.group.setRoleSystem(false);
//        	this.group.setAuthority(WebConstants.ROLE_USER);
        	this.group.setMenus(menus);
        }
        try {
        	mgr.save(group);
        } catch (Exception e) {
        	// TODO: handle exception
        	e.printStackTrace();
        }
              
        
        List<Object> args = new ArrayList<Object>();
        args.add(group.getName());
        
        ActionContext.getContext().getSession().put("message", getText("L\u01B0u d\u1EEF li\u1EC7u th\u00E0nh c\u00F4ng! ", args));
                
        return SUCCESS;
    }
    
    public String search() {
        if (log.isDebugEnabled()) {
            log.debug("entering 'search' method");
        }		
		if(group!=null && !"".equals(group.getName()))  {
			
			groups = this.mgr.search(group);
		}
		
		return SUCCESS;
	}
    
    
    public void setCancel(String cancel) {
        this.cancel = cancel;
    }
    
    public void setDelete(String delete) {
        this.delete = delete;
    }
    
    public void setGroup(Group group) {
		this.group = group;
	}
    
    public void setGroupManager(GroupManager groupManager) {
        this.mgr = groupManager;
    }
    
    public void setGroups(List<Group> groups) {
		this.groups = groups;
	}


	public void setLstAllMenu(List<Menu> lstAllMenu) {
		this.lstAllMenu = lstAllMenu;
	}

	public void setLstPermissionMenu(List<String> lstPermissionMenu) {
		this.lstPermissionMenu = lstPermissionMenu;
	}

	public void setLstSelectedMenu(List<Menu> lstSelectedMenu) {
		this.lstSelectedMenu = lstSelectedMenu;
	}

	public void setMenuManager(MenuManager menuManager) {
		this.menuManager = menuManager;
	}

	@Autowired
	public void setMenuTreeManager(MenuTreeManager menuTreeManager) {
		this.menuTreeManager = menuTreeManager;
	}

	public void setMgr(GroupManager mgr) {
		this.mgr = mgr;
	}

	public void setSearch(String search) {
		this.search = search;
	}

	public void setUserManager(UserManager userManager) {
		this.userManager = userManager;
	}

	public void setUsers(List<User> users) {
		this.users = users;
	}
	@Override
	public Long getId() {
		
		return (group==null? id : group.getId());//id
	}

    
}
